package com.yangtao.prototype.common.freemarker;

import com.yangtao.framework.common.Option;
import com.yangtao.framework.service.ServiceLocator;
import com.yangtao.prototype.master.constant.service.ConstantService;
import freemarker.core.Environment;
import freemarker.ext.beans.StringModel;
import freemarker.template.*;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang.xwork.StringUtils;

import java.io.IOException;
import java.util.List;
import java.util.Map;

/**
 * 常量下拉单的宏，用于产生产量下拉单
 * 参数：
 * type 产量的类型，必须输入参数
 * id dojo组件的id，需要在html范围内唯一
 * name html 标签的name属性
 * style html 标签的style属性
 * class html 标签的calss属性
 * value html 标签的value属性，用于指定哪个选中
 * hasEmpty 布尔值，是否有空选项，默认为否
 * emptyKey 空选项的值 默认为半角空格(因为在dojo中无法定义空字符串为value，故使用半角空格) " "
 * emptyText 空选项的显示文本，默认为"请选择"
 * 使用示例
 * <@const type="weight" id="xx" name="xx" style="" class="" value="xx" hasEmpty=true emptyKey="all" emptyText="全部"></const>
 * <@const type="weight" id="xx" name="xx" style="" class="" value="xx" ></const>
 * 注意事项：
 * 此组件使用的是dojo的dijit.form.Select组件，如果没有引入这个组件，需要加上dojo.require("dijit.form.Select")
 *
 * @author 杨涛
 * @version 1.0
 */
public class ConstantDirective implements TemplateDirectiveModel {

	@Override
	public void execute(Environment env, Map params, TemplateModel[] loopVars,
	                    TemplateDirectiveBody body) throws TemplateException, IOException {
		//TODO 从上下文中取出用户ID和公司ID
		// type
		String typeStr = null;
		TemplateModel type = (TemplateModel) params.get("type");
		if (type == null) {
			throw new TemplateModelException("参数：type 不能为空");
		}
		if (type instanceof SimpleScalar) {
			typeStr = ((SimpleScalar) type).getAsString();
		}
		if (type instanceof StringModel) {
			typeStr = ((StringModel) type).getAsString();
		}
		if (StringUtils.isBlank(typeStr)) {
			throw new TemplateModelException("参数：type 不能为空");
		}

		// name
		String nameStr = "";
		TemplateModel name = (TemplateModel) params.get("name");
		if (name != null) {
			if (name instanceof SimpleScalar) {
				nameStr = ((SimpleScalar) name).getAsString();
			}
			if (name instanceof StringModel) {
				nameStr = ((StringModel) name).getAsString();
			}
		}

		// id
		String idStr = "";
		TemplateModel id = (TemplateModel) params.get("id");
		if (id != null) {
			if (id instanceof SimpleScalar) {
				idStr = ((SimpleScalar) id).getAsString();
			}
			if (id instanceof StringModel) {
				idStr = ((StringModel) id).getAsString();
			}
		}
		// style
		String styleStr = "width:100px";
		TemplateModel style = (TemplateModel) params.get("style");
		if (style != null) {
			if (style instanceof SimpleScalar) {
				styleStr = ((SimpleScalar) style).getAsString();
			}
			if (style instanceof StringModel) {
				styleStr = ((StringModel) style).getAsString();
			}
		}
		// value
		String valueStr = "";
		TemplateModel value = (TemplateModel) params.get("value");
		if (value != null) {
			if (value instanceof SimpleScalar) {
				valueStr = ((SimpleScalar) value).getAsString();
			}
			if (value instanceof StringModel) {
				valueStr = ((StringModel) value).getAsString();
			}
		}
		// class
		String classStr = "";
		TemplateModel styleclass = (TemplateModel) params.get("class");
		if (styleclass != null) {
			if (styleclass instanceof SimpleScalar) {
				classStr = ((SimpleScalar) styleclass).getAsString();
			}
			if (styleclass instanceof StringModel) {
				classStr = ((StringModel) styleclass).getAsString();
			}
		}
		// islabel
		boolean islabel = false;
		TemplateModel islabelModel = (TemplateModel) params.get("islabel");
		if (islabelModel != null) {
			if (islabelModel instanceof TemplateBooleanModel) {
				islabel = ((TemplateBooleanModel) islabelModel).getAsBoolean();
			}
		}
		//是否有空选项
		// hasEmpty
		boolean hasEmpty = false;
		TemplateModel hasEmptyModel = (TemplateModel) params.get("hasEmpty");
		if (hasEmptyModel != null) {
			if (hasEmptyModel instanceof TemplateBooleanModel) {
				hasEmpty = ((TemplateBooleanModel) hasEmptyModel)
						.getAsBoolean();
			}
		}
		//空选项的值
		String emptyKeyStr = " ";
		TemplateModel emptyKey = (TemplateModel) params.get("emptyKey");
		if (emptyKey != null) {
			if (emptyKey instanceof SimpleScalar) {
				emptyKeyStr = ((SimpleScalar) styleclass).getAsString();
			}
			if (emptyKey instanceof StringModel) {
				emptyKeyStr = ((StringModel) styleclass).getAsString();
			}
		}

		//空选项的显示文本
		String emptyTextStr = "请选择";
		TemplateModel emptyText = (TemplateModel) params.get("emptyText");
		if (emptyText != null) {
			if (emptyText instanceof SimpleScalar) {
				emptyTextStr = ((SimpleScalar) styleclass).getAsString();
			}
			if (emptyText instanceof StringModel) {
				emptyTextStr = ((StringModel) styleclass).getAsString();
			}
		}
		StringBuilder sb = new StringBuilder();
		if (islabel) {
			sb.append("<label name=\"");
			sb.append(nameStr);
			sb.append("\" ");
			sb.append(" id=\"");
			sb.append(idStr);
			sb.append("\" ");
			sb.append("style=\"");
			sb.append(styleStr);
			sb.append("\" ");
			sb.append(" class=\"");
			sb.append(classStr);
			sb.append("\" >");
			String text = findValue(typeStr, valueStr);
			if (text != null) {
				sb.append(text);
			}
			sb.append("</label>");
		} else {
			sb.append("<select");
			sb.append(" ").append("name=\"").append(nameStr).append("\"");
			sb.append(" ").append("id=\"").append(idStr).append("\"");
			sb.append(" ").append("style=\"").append(styleStr).append("\"");
			sb.append(" ").append("class=\"").append(classStr).append("\"");
			sb.append(" ").append("dojoType=\"").append("dijit.form.Select").append("\"");
			sb.append(" ").append(">");

			List<Option> keyValuePair = findConstByType(typeStr);
			//加上空选项
			if (hasEmpty) {
				sb.append("<option value=\"" + emptyKeyStr + "\">")
						.append(emptyTextStr).append("</option>");
			}
			if (CollectionUtils.isNotEmpty(keyValuePair)) {
				for (Option option : keyValuePair) {
					sb.append("<option value=\"" + option.getValue() + "\"");
					if (valueStr.equals(option.getValue())) {
						sb.append(" selected=\"selected\"");
					}
					sb.append(" >").append(option.getText()).append("</option>");
				}
			}
			sb.append("</select>");
//			String storeKey = "__" + typeStr + "Store";
//			if (env.__getitem__(storeKey) == null) {
//				sb.append("\n");
//				List<Option> keyValuePair = findConstByType(typeStr);
//				sb.append(buildStore(keyValuePair, typeStr));
//				env.__setitem__(storeKey, 1);
//			}
//			if()

//			for (Option option : keyValuePair) {
//				sb.append(" <option value=\"");
//				sb.append(option.getValue());
//				sb.append("\"  ");
//				if (option.getValue().equals(valueStr)) {
//					sb.append(" selected ");
//				}
//				sb.append(" >");
//				sb.append(option.getText());
//				sb.append("</option> ");
//			}
//			sb.append("</select>");
		}
		env.getOut().write(sb.toString());
	}

	/**
	 * 根据设置生成下拉单的外观
	 *
	 * @param keyValuePair 键值对
	 * @return
	 */
	private String buildStore(List<Option> keyValuePair, String type) {
		StringBuilder sb = new StringBuilder();
		sb.append("<script type=\"text/javascript\">").append("\n");
		sb.append("\tvar " + type + "Store = new dojo.data.ItemFileReadStore({");
		sb.append("\n");
		sb.append("\t\tdata:{");
		sb.append("\n");
		sb.append("\t\t\tidentifier:\"value\"");
		sb.append("\n");
		sb.append("\t\t\t,label:\"text\"");
		sb.append("\n");
		sb.append("\t\t\t,items:[");
		sb.append("\n");
		for (int k = 0; k < keyValuePair.size(); k++) {
			Option option = keyValuePair.get(k);
			if (k > 0) {
				sb.append("\t\t\t\t,");
			} else {
				sb.append("\t\t\t\t");
			}
			sb.append("{value:\"" + option.getValue() + "\",text:\"" + option.getText() + "\"}");
			sb.append("\n");
		}
		sb.append("\t\t\t]");
		sb.append("\n");
		sb.append("\t\t}");
		sb.append("\n");
		sb.append("\t});");
		sb.append("</script>");
		return sb.toString();
	}

	/**
	 * 根据类型查询选项
	 *
	 * @param type 类型
	 * @return 类型列表
	 */
	private List<Option> findConstByType(String type) {
		ConstantService constantService = ServiceLocator.getInstance().getService(ConstantService.class);
		return constantService.findByType(type);
	}

	/**
	 * 根据常量代码和常量类型，取得常量值
	 *
	 * @param type
	 * @param code
	 * @return
	 */
	private String findValue(String type, String code) {
		ConstantService constantService = ServiceLocator.getInstance().getService(ConstantService.class);
		return constantService.findValue(type, code);
	}
}
